mod handlers;
mod models;
mod utils;

use handlers::{handle_question, is_kb_duplicated, list_kb_number};
use models::ProjectConfig;
use rfd::MessageDialog;
use std::fs::OpenOptions;
use std::io::Write;
use utils::{
    build_args, check_ai_flag, file_ops, git, load_long_question, load_system_message,
    project_question, write_long_question,
};

#[tokio::main]
async fn main() {
    let check_ai_flag_result = &match check_ai_flag() {
        Ok(result) => result,
        Err(err) => panic!("{:?}", err),
    };

    if check_ai_flag_result.no_ai_flag {
        panic!(
            "{}目录下不存在{}",
            check_ai_flag_result.root_path.display(),
            check_ai_flag_result.flag_name
        );
    }

    let matches_result = build_args();

    if matches_result.list_kb {
        if let Err(err) = list_kb_number() {
            eprintln!("{:?}", err);
        }
        return;
    }

    if is_kb_duplicated(&matches_result.to_kb.as_ref()) {
        panic!("存在重复的kb名称:{}", matches_result.to_kb.unwrap());
    }

    println!(
        "working path:{}",
        check_ai_flag_result.working_path.to_string_lossy()
    );
    println!("temperature:{}", matches_result.temperature);
    println!(
        "history_count:{}\nloading...\n",
        matches_result.history_count
    );

    if let Some(project_config) = ProjectConfig::load() {
        if let Some(project_content) =
            project_question::load_long_question_from_project(&project_config)
        {
            println!(
                "process file:{}",
                project_content.file_path.to_string_lossy()
            );

            match git::is_file_check_out(&project_content.file_path) {
                Ok(result) => {
                    if result {
                        panic!(
                            "请确保该文件`{}`是签入状态",
                            project_content.file_path.to_string_lossy()
                        );
                    }
                }
                Err(e) => {
                    panic!("文件git检查失败:{}", e);
                }
            }

            let _ = write_long_question(
                &check_ai_flag_result.working_path,
                Some(&project_content.content),
            );

            match handle_question(
                &load_system_message(),
                &project_content.content,
                matches_result.history_count,
                &check_ai_flag_result.working_path,
                &matches_result.to_kb.as_ref(),
                &matches_result.kb_number,
                matches_result.temperature,
                &Some(project_config),
            )
            .await
            {
                Ok(message) => {
                    MessageDialog::new()
                        .set_title("通知")
                        .set_description(format!(
                            "文件处理完毕:{}",
                            project_content.file_path.to_string_lossy()
                        ))
                        .show();
                }
                Err(err) => eprintln!("{:?}", err),
            };
        } else {
            println!("没有发现需要处理的文件, 请检查config.yml中是否包含了需要处理的文件扩展名");
        }
    } else if matches_result.short_question.is_none() && matches_result.use_long_question {
        let long_question = match load_long_question(&check_ai_flag_result.working_path) {
            Ok(result) => result,
            Err(err) => panic!("{:?}", err),
        };
        if let Err(err) = handle_question(
            &load_system_message(),
            &long_question,
            matches_result.history_count,
            &check_ai_flag_result.working_path,
            &matches_result.to_kb.as_ref(),
            &matches_result.kb_number,
            matches_result.temperature,
            &None,
        )
        .await
        {
            eprintln!("{:?}", err);
        };
    } else if let Some(question) = matches_result.short_question {
        if let Err(err) = handle_question(
            &load_system_message(),
            &question,
            matches_result.history_count,
            &check_ai_flag_result.working_path,
            &matches_result.to_kb.as_ref(),
            &matches_result.kb_number,
            matches_result.temperature,
            &None,
        )
        .await
        {
            eprintln!("{:?}", err);
        };
    } else {
        panic!("无效参数输入");
    }
}
